﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using SurveySystem.Repository;
using SurveySystem.Model;

namespace SurveySystem.Factory
{
    /// <summary>
    /// Factory class for working with survey responses
    /// </summary>
    public class ResultFactory
    {
        private ISurveyResponseRepository _responseRepository;
        private ISurveyResponseAnswerRepository _responseAnswerRepository;

        public ResultFactory(ISurveyResponseRepository responseRepository, ISurveyResponseAnswerRepository responseAnswerRepository)
        {
            _responseRepository = responseRepository;
            _responseAnswerRepository = responseAnswerRepository;
        }

        /// <summary>
        /// Submits a response against a specified survey. 
        /// </summary>
        /// <param name="s"></param>
        /// <param name="response"></param>
        public void SubmitResults(Survey s, Response response)
        {
            // assign the survey ID
            response.SurveyID = s.SurveyID;

            // submit the response object
            _responseRepository.AddResponse(response);

            // submit each answers
            foreach (ResponseAnswer ra in response.Answers)
            {
                // assign the new responseID which was created by AddResponse(..)
                ra.ResponseID = response.ResponseID;

                _responseAnswerRepository.AddResponseAnswer(ra);
            }
        }

        /// <summary>
        /// Gets a <see cref="Response"/> object from the give repository and populates it before returning
        /// </summary>
        /// <param name="responseID"></param>
        /// <returns></returns>
        /// <seealso cref="PopulateResponse"/>
        public Response GetPopulatedResponse(int responseID)
        {
            Response r = _responseRepository.GetResponseByID(responseID);

            PopulateResponse(r);

            return r;
        }

        /// <summary>
        /// Populates a <see cref="Response"/>'s list of <see cref="ResponseAnswer"/>s
        /// </summary>
        /// <param name="r"></param>
        public void PopulateResponse(Response r)
        {
            // response not found, return null
            if (r == null)
                return;


            // empty the answers list
            r.Answers.Clear();

            // get the ResponseAnswers from the repository
            List<ResponseAnswer> answers = _responseAnswerRepository.GetResponseAnswersForResponse(r.ResponseID);

            // loop through each question
            foreach (ResponseAnswer ra in answers)
            {
                // add the ResponseAnswer to the Response object
                r.Answers.Add(ra);
            }

        }

        /// <summary>
        /// Creates a new <see cref="Response"/> object, populating the field values and filling the answer list
        /// with the supplied list of <see cref="ResponseAnswer"/>. This method does NOT submit answers to the 
        /// given repositories - for that, see <see cref="SubmitResults"/>
        /// </summary>
        /// <param name="s"></param>
        /// <param name="answers"></param>
        /// <returns></returns>
        public Response CreateResponse(Survey s, List<ResponseAnswer> answers)
        {
            Response response = new Response();
            response.SurveyID = s.SurveyID;
            response.ParticipantID = "";
            response.Machine = System.Environment.MachineName;
            response.ResponseTime = DateTime.Now;

            response.Answers.AddRange(answers);

            return response;
        }

    }
}
